﻿using HSDc.RingleFlow.Api.Service;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System;
using HSDc.RingleFlow.Api.Kernel;
using HSDc.RingleFlow.Api.Factory;
using HSDc.RingleFlow.Api;
using System.Collections.Generic;
using HSDc.RingleFlow.Api.Kernel.History;

namespace TestRingleFlow
{
    
    
    /// <summary>
    ///This is a test class for IRepositoryServiceTest and is intended
    ///to contain all IRepositoryServiceTest Unit Tests
    ///</summary>
    [TestClass()]
    public class IRepositoryServiceTest
    {


        private TestContext testContextInstance;

        /// <summary>
        ///Gets or sets the test context which provides
        ///information about and functionality for the current test run.
        ///</summary>
        public TestContext TestContext
        {
            get
            {
                return testContextInstance;
            }
            set
            {
                testContextInstance = value;
            }
        }

        #region Additional test attributes
        // 
        //You can use the following additional attributes as you write your tests:
        //
        //Use ClassInitialize to run code before running the first test in the class
        //[ClassInitialize()]
        //public static void MyClassInitialize(TestContext testContext)
        //{
        //}
        //
        //Use ClassCleanup to run code after all tests in a class have run
        //[ClassCleanup()]
        //public static void MyClassCleanup()
        //{
        //}
        //
        //Use TestInitialize to run code before running each test
        //[TestInitialize()]
        //public void MyTestInitialize()
        //{
        //}
        //
        //Use TestCleanup to run code after each test has run
        //[TestCleanup()]
        //public void MyTestCleanup()
        //{
        //}
        //
        #endregion


        internal virtual IRepositoryService CreateIRepositoryService()
        {
            // 透過Factory取得WorkflowEngine的實體
            IWorkflowEngine engine = WorkflowEngineFactory.GetInstance();
            // 取得Repository Service
            IRepositoryService repositoryService = engine.RespositoryService;
            // 取得Runtime Service
            IRuntimeService runtimeService = engine.RuntimeService;
            // 取得Task Service
            ITaskService taskService = engine.TaskService;
            // 取得Organization Service
            IOrganisationService organizationService = engine.OrgaisationService;
            // 取得History Service
            IHistoryService historyService = engine.HistoryService;
            return repositoryService;
        }

        /// <summary>
        ///A test for GetProcessDefinition
        ///</summary>
        [TestMethod()]
        public void GetProcessDefinitionTest()
        {
            IRepositoryService target = CreateIRepositoryService();
            string processDefinitionId = "83CEDA43-0E89-4F57-95D7-553FCF721A38";
            string expectedName = "請假流程";
            IProcessDefinition actual;
            actual = target.GetProcessDefinition(processDefinitionId);
            Assert.AreEqual(expectedName, actual.Name);
        }

        /// <summary>
        ///A test for GetProcessDefinitionByName
        ///</summary>
        [TestMethod()]
        public void GetProcessDefinitionByNameTest()
        {
            IRepositoryService target = CreateIRepositoryService();
            string processDefinitionName = "請假流程";
            string expectedId = "83CEDA43-0E89-4F57-95D7-553FCF721A38";
            IProcessDefinition actual;
            actual = target.GetProcessDefinitionByName(processDefinitionName);
            Assert.AreEqual(expectedId, actual.Id);
        }

        public void GetProcessInstance()
        {
            IWorkflowEngine engine = WorkflowEngineFactory.GetInstance();
            IRepositoryService repositoryService = engine.RespositoryService;
            string processDefinitionId = "83CEDA43-0E89-4F57-95D7-553FCF721A38";
            string instanceId = "83CEDA43-0E89-4F57-95D7-553FCF721A38";
            string taskId = "83CEDA43-0E89-4F57-95D7-553FCF721A38";
            string userId = "ringle";
            IProcessDefinition processDefinition = repositoryService.GetProcessDefinition(processDefinitionId);
            IRuntimeService runtimeService = engine.RuntimeService;
            ITaskService taskService = engine.TaskService;
            IHistoryService historyService = engine.HistoryService;
            Dictionary<string, object> variables = new Dictionary<string, object>();
            variables.Add("Test Variable", "Testing....");
            IProcessInstance instance = runtimeService.CreateProcessInstance(processDefinition);
            instance = runtimeService.CreateProcessInstance(processDefinitionId);
            instance = runtimeService.CreateProcessInstance(processDefinition, variables);
            instance = runtimeService.CreateProcessInstance(processDefinitionId, variables);
            // 透過流程instance id取得特定的流程instance
            instance = runtimeService.GetProcessInstance(instanceId);
            // 強制結束某個特定的流程instance
            runtimeService.CompleteProcessInstance(instance);
            // 透過runtimeService取得流程變數
            variables = runtimeService.GetVariables(instanceId);
            // 透過runtimeService取得特定流程變數
            object variable = runtimeService.GetVaraible(instanceId, "Test Variable");
            // 透過流程Instance取得流程變數
            variables = instance.GetVaraibles();
            // 透過流程Instance取得特定流程變數
            variable = instance.GetVaraible("Test Variable");
            // 透過使用者ID取得該使用者所有的工作
            List<ITask> tasks = taskService.GetTasks(userId);
            // 透過Task ID取得某個特定的工作
            ITask task = taskService.GetTask(taskId);
            // 透過使用者ID以及特定的ProcessInstanceID取得特定的工作
            task = taskService.GetTask(userId, instanceId);
            // 暫存某個工作
            taskService.SaveTask(task);
            // 完成某個工作
            taskService.CompleteTask(task);
            // 改變某個工作的負責人
            task.ChangeAssignee("steve");
            // 加入變數到某個特定的工作中
            task.AddVariable("Test Task Var", "Testing Variables.....");
            // 取得所有關卡的資料
            AuditVdb auditInfo = historyService.RetrieveAuditInfo(instanceId);
        }
    }
}
